package com.tran.tr.common.id;

import java.text.SimpleDateFormat;

public class SnowflakeIdWorker {

	public static String getId() {
		return String.valueOf(SnowflakeIdWorker.getGeneralId());
	}

	private static long BEIGIN_TIME;

	// 每一个id的标识位，用于标识同一个服务相同毫秒的生成id的区分,占12位
	private static int INDEX = 0;

	// 服务唯一标识从0到2043,占10位
	private final static int SERVICE_ID = 30;

	// 由于id的标识index占了最低的12位，因此，服务左移12位，与index 左或运算，生成新的22位字节，
	// 高10位为服务id，低12位为index
	private final static int SERVICE_ID_SHIFT_LEFT = 12;

	// 时间戳，占41位，
	private static long TIME_TAMP = 0L;

	// 由于上面serviceId 和index 分别占据了10 和 12 位，因此，时间戳要左移22位，与serviceid 和 index 做与运算，
	// 最终生成63位新数据， 时间戳占据前面41位， 后面22位为 serviceId 占据10位和index占据12位
	private final static int TIME_TAMP__SHIFT_LEFT = 22;

	private static SnowflakeIdWorker generalId = new SnowflakeIdWorker();

	private SnowflakeIdWorker() {
		String sdate = "2018-08-08 00-00-00";
		SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd HH-mm-ss");
		try {
			BEIGIN_TIME = simpleDateFormat.parse(sdate).getTime();
		} catch (Exception e) {
			e.printStackTrace();
		}
		TIME_TAMP = System.currentTimeMillis() - BEIGIN_TIME;
	}

	public static synchronized long getGeneralId() {

		long current_time_tamp = System.currentTimeMillis() - BEIGIN_TIME;
		if (current_time_tamp != TIME_TAMP) {// 如果不是统一个时间戳内，重置时间戳和序列号
			TIME_TAMP = current_time_tamp;
			INDEX = 0;
		}
		// 每次生成id序列号加1
		INDEX++;
		long new_service_id = SERVICE_ID << SERVICE_ID_SHIFT_LEFT; // 服务唯一标识左移12位，占据最终63位二进制的22到12
		long new_time_tamp = TIME_TAMP << TIME_TAMP__SHIFT_LEFT;// 时间戳左移22位，占据最终63位二进制的23到63

		return new_time_tamp | new_service_id | INDEX;

	}

	public static void main(String[] args) {

		for (int i = 0; i < 10; i++) {
			System.out.println(SnowflakeIdWorker.getGeneralId());
		}
	}
}
